import {
	Injectable,
	NotFoundException,
	BadRequestException,
} from "@nestjs/common";
import { InjectRepository } from "@nestjs/typeorm";
import { Repository } from "typeorm";
import { Order } from "./entities/order.entity";
import { OrderItem } from "./entities/order-item.entity";
import { CreateOrderDto } from "./dto/create-order.dto";
import { UpdateOrderDto } from "./dto/update-order.dto";
import { UserService } from "../user/user.service";
import { ProductService } from "../product/product.service";
import { PointsService } from "../points/points.service";
import { Logger } from "@nestjs/common";

@Injectable()
export class OrderService {
	private readonly logger = new Logger(OrderService.name);

	constructor(
		@InjectRepository(Order)
		private orderRepository: Repository<Order>,
		@InjectRepository(OrderItem)
		private orderItemRepository: Repository<OrderItem>,
		private userService: UserService,
		private productService: ProductService,
		private pointsService: PointsService
	) {}

	async findAll(query: any): Promise<[Order[], number]> {
		const {
			userId,
			status,
			orderNo,
			startDate,
			endDate,
			page = 1,
			limit = 10,
		} = query;

		// 使用queryBuilder进行查询
		const queryBuilder = this.orderRepository.createQueryBuilder("order");
		queryBuilder.leftJoinAndSelect("order.items", "items");
		queryBuilder.leftJoinAndSelect("items.product", "product");

		// 条件过滤
		if (userId) {
			queryBuilder.andWhere("order.userId = :userId", { userId });
		}

		if (status) {
			// 处理状态数组
			if (Array.isArray(status)) {
				queryBuilder.andWhere("order.status IN (:...status)", { status });
			} else {
				queryBuilder.andWhere("order.status = :status", { status });
			}
		}

		if (orderNo) {
			queryBuilder.andWhere("order.orderNo LIKE :orderNo", {
				orderNo: `%${orderNo}%`,
			});
		}

		if (startDate) {
			queryBuilder.andWhere("order.createdAt >= :startDate", {
				startDate: `${startDate} 00:00:00`,
			});
		}

		if (endDate) {
			queryBuilder.andWhere("order.createdAt <= :endDate", {
				endDate: `${endDate} 23:59:59`,
			});
		}

		// 分页
		queryBuilder.skip((page - 1) * limit);
		queryBuilder.take(limit);

		// 排序
		queryBuilder.orderBy("order.id", "DESC");

		const [orders, total] = await queryBuilder.getManyAndCount();

		// 对于没有加载到订单项的订单，手动加载
		for (const order of orders) {
			if (!order.items || order.items.length === 0) {
				const orderItems = await this.orderItemRepository.find({
					where: { orderId: order.id },
					relations: ["product"],
				});

				if (orderItems && orderItems.length > 0) {
					order.items = orderItems;

					// 确保每个订单项都有商品图片
					for (const item of orderItems) {
						if (item.product && !item.image) {
							item.image = item.product.image;
						}
					}
				}
			}
		}

		return [orders, total];
	}

	async findOne(id: number): Promise<Order> {
		const order = await this.orderRepository.findOne({
			where: { id },
			relations: ["user", "items", "items.product"],
		});

		if (!order) {
			throw new NotFoundException(`订单ID为${id}的订单不存在`);
		}

		// 手动加载订单项
		if (!order.items || order.items.length === 0) {
			const orderItems = await this.orderItemRepository.find({
				where: { orderId: id },
				relations: ["product"],
			});

			if (orderItems && orderItems.length > 0) {
				order.items = orderItems;
			}
		}

		return order;
	}

	async findByUserId(userId: number, query: any): Promise<[Order[], number]> {
		// 使用queryBuilder进行查询
		const { status, orderNo, startDate, endDate, page = 1, limit = 10 } = query;

		const queryBuilder = this.orderRepository.createQueryBuilder("order");
		queryBuilder.leftJoinAndSelect("order.items", "items");
		queryBuilder.leftJoinAndSelect("items.product", "product");

		// 条件过滤
		queryBuilder.where("order.userId = :userId", { userId });

		if (status) {
			// 处理状态数组
			if (Array.isArray(status)) {
				queryBuilder.andWhere("order.status IN (:...status)", { status });
			} else {
				queryBuilder.andWhere("order.status = :status", { status });
			}
		}

		if (orderNo) {
			queryBuilder.andWhere("order.orderNo LIKE :orderNo", {
				orderNo: `%${orderNo}%`,
			});
		}

		if (startDate) {
			queryBuilder.andWhere("order.createdAt >= :startDate", {
				startDate: `${startDate} 00:00:00`,
			});
		}

		if (endDate) {
			queryBuilder.andWhere("order.createdAt <= :endDate", {
				endDate: `${endDate} 23:59:59`,
			});
		}

		// 分页
		queryBuilder.skip((page - 1) * limit);
		queryBuilder.take(limit);

		// 排序
		queryBuilder.orderBy("order.id", "DESC");

		const [orders, total] = await queryBuilder.getManyAndCount();

		// 对于没有加载到订单项的订单，手动加载
		for (const order of orders) {
			if (!order.items || order.items.length === 0) {
				const orderItems = await this.orderItemRepository.find({
					where: { orderId: order.id },
					relations: ["product"],
				});

				if (orderItems && orderItems.length > 0) {
					order.items = orderItems;

					// 确保每个订单项都有商品图片
					for (const item of orderItems) {
						if (item.product && !item.image) {
							item.image = item.product.image;
						}
					}
				}
			}
		}

		return [orders, total];
	}

	async create(createOrderDto: CreateOrderDto): Promise<Order> {
		const { userId, items, receiver, phone, address, remark } = createOrderDto;

		// 检查用户是否存在
		const user = await this.userService.findOne(userId);

		// 计算订单总积分
		let totalPoints = 0;
		const orderItems = [];

		// 检查商品库存并计算总积分
		for (const item of items) {
			// 检查是否有SKU
			if (item.skuId) {
				// 获取SKU信息
				const sku = await this.orderRepository.manager
					.getRepository("product_skus")
					.findOne({
						where: { id: item.skuId },
						relations: ["product"],
					});

				if (!sku) {
					throw new BadRequestException(`SKU ID为${item.skuId}的SKU不存在`);
				}

				const product = sku.product;

				if (sku.availableStock < item.quantity) {
					throw new BadRequestException(`商品 ${product.name} 的SKU库存不足`);
				}

				if (product.status !== "在售") {
					throw new BadRequestException(`商品 ${product.name} 已下架`);
				}

				const itemTotalPoints = sku.price * item.quantity;
				totalPoints += itemTotalPoints;

				orderItems.push({
					productId: product.id,
					productName: product.name,
					skuId: sku.id,
					skuSpecs: sku.specs,
					quantity: item.quantity,
					points: sku.price,
					totalPoints: itemTotalPoints,
					image: sku.image || product.image,
				});
			} else {
				// 常规商品处理
				const product = await this.productService.findOne(item.productId);

				// 商品库存现在是通过SKU计算的虚拟字段
				if (product.availableStock < item.quantity) {
					throw new BadRequestException(`商品 ${product.name} 库存不足`);
				}

				if (product.status !== "在售") {
					throw new BadRequestException(`商品 ${product.name} 已下架`);
				}

				const itemTotalPoints = product.price * item.quantity;
				totalPoints += itemTotalPoints;

				orderItems.push({
					productId: product.id,
					productName: product.name,
					quantity: item.quantity,
					points: product.price,
					totalPoints: itemTotalPoints,
					image: product.image,
				});
			}
		}

		// 检查用户积分是否足够
		if (user.points < totalPoints) {
			throw new BadRequestException("用户积分不足");
		}

		// 生成订单号
		const orderNo = `O${Date.now()}${Math.floor(Math.random() * 1000)}`;

		// 获取当前时间
		const now = new Date();

		try {
			// 减少可用库存
			await this.reduceAvailableStock(items);

			// 创建订单
			const order = this.orderRepository.create({
				orderNo,
				userId,
				totalPoints,
				status: "待付款",
				receiver,
				phone,
				address,
				remark,
				createdAt: now,
				updatedAt: now,
			});

			const savedOrder = await this.orderRepository.save(order);

			// 创建订单项
			const orderItemsWithOrderId = orderItems.map((item) => ({
				...item,
				orderId: savedOrder.id,
			}));

			await this.orderItemRepository.save(orderItemsWithOrderId);

			return this.findOne(savedOrder.id);
		} catch (error) {
			// 如果创建订单失败，恢复可用库存
			await this.restoreAvailableStock(items);
			throw error;
		}
	}

	async update(id: number, updateOrderDto: UpdateOrderDto): Promise<Order> {
		const order = await this.findOne(id);

		// 如果更新状态为已发货，检查原状态是否为待发货
		if (updateOrderDto.status === "已发货" && order.status !== "待发货") {
			throw new BadRequestException("只有待发货的订单才能更新为已发货");
		}

		// 如果更新状态为已完成，检查原状态是否为已发货
		if (updateOrderDto.status === "已完成" && order.status !== "已发货") {
			throw new BadRequestException("只有已发货的订单才能更新为已完成");
		}

		// 如果更新状态为已取消，检查原状态
		if (updateOrderDto.status === "已取消") {
			if (order.status !== "待付款" && order.status !== "待发货") {
				throw new BadRequestException("只有待付款或待发货的订单才能取消");
			}

			// 如果是从待发货状态取消，需要恢复商品库存和退还用户积分
			if (order.status === "待发货") {
				await this.restoreProductStock(order);

				// 退还用户积分
				await this.pointsService.create({
					userId: order.userId,
					type: "收入",
					amount: order.totalPoints,
					description: `订单 ${order.orderNo} 取消退款`,
					orderId: order.id,
				});

				this.logger.log(
					`订单 ${order.id} 取消，退还用户 ${order.userId} 积分 ${order.totalPoints}`
				);
			}
		}

		// 如果订单状态从待付款变为待发货，扣除用户积分并减少商品实际库存
		if (order.status === "待付款" && updateOrderDto.status === "待发货") {
			// 扣除用户积分
			await this.pointsService.create({
				userId: order.userId,
				type: "支出",
				amount: order.totalPoints,
				description: `订单 ${order.orderNo} 支付`,
				orderId: order.id,
			});

			// 减少商品实际库存
			await this.reduceProductStock(order);
		}

		Object.assign(order, updateOrderDto);
		return this.orderRepository.save(order);
	}

	// 减少商品库存
	private async reduceProductStock(order: Order): Promise<void> {
		// 确保订单项已加载
		if (!order.items || order.items.length === 0) {
			const orderItems = await this.orderItemRepository.find({
				where: { orderId: order.id },
				relations: ["product", "sku"],
			});
			order.items = orderItems;
		}

		// 遍历订单项，减少对应商品的实际库存
		for (const item of order.items) {
			// 如果有SKU，减少SKU的实际库存
			if (item.skuId) {
				// 使用 TypeORM 的 EntityManager 来更新 SKU 库存
				await this.orderRepository.manager
					.getRepository("product_skus")
					.decrement({ id: item.skuId }, "stock", item.quantity);
				this.logger.log(`SKU ${item.skuId} 实际库存减少 ${item.quantity}`);
			} else {
				// 我们不再直接更新商品的stock字段，因为它现在是计算属性
				// 需要找到商品的所有SKU并相应调整
				const product = await this.productService.findOne(item.productId);
				if (product.skus && product.skus.length > 0) {
					// 如果有SKU，分配数量到第一个有足够库存的SKU
					for (const sku of product.skus) {
						if (sku.stock >= item.quantity) {
							await this.orderRepository.manager
								.getRepository("product_skus")
								.decrement({ id: sku.id }, "stock", item.quantity);
							this.logger.log(
								`商品 ${item.productId} 的SKU ${sku.id} 实际库存减少 ${item.quantity}`
							);
							break;
						}
					}
				} else {
					this.logger.warn(`商品 ${item.productId} 没有SKU，无法减少实际库存`);
				}
			}
		}
	}

	// 恢复商品库存
	private async restoreProductStock(order: Order): Promise<void> {
		// 确保订单项已加载
		if (!order.items || order.items.length === 0) {
			const orderItems = await this.orderItemRepository.find({
				where: { orderId: order.id },
				relations: ["product", "sku"],
			});
			order.items = orderItems;
		}

		// 遍历订单项，恢复对应商品的实际库存和可用库存
		for (const item of order.items) {
			// 如果有SKU，恢复SKU的实际库存和可用库存
			if (item.skuId) {
				// 恢复SKU的实际库存
				await this.orderRepository.manager
					.getRepository("product_skus")
					.increment({ id: item.skuId }, "stock", item.quantity);

				// 恢复SKU的可用库存
				await this.orderRepository.manager
					.getRepository("product_skus")
					.increment({ id: item.skuId }, "availableStock", item.quantity);

				this.logger.log(`SKU ${item.skuId} 库存恢复 ${item.quantity}`);
			} else {
				// 如果没有SKU，则需要找到商品的SKU来恢复库存
				const product = await this.productService.findOne(item.productId);
				if (product.skus && product.skus.length > 0) {
					// 恢复第一个SKU的库存（或者找到之前扣减的SKU）
					const sku = product.skus[0];
					// 恢复SKU的实际库存
					await this.orderRepository.manager
						.getRepository("product_skus")
						.increment({ id: sku.id }, "stock", item.quantity);

					// 恢复SKU的可用库存
					await this.orderRepository.manager
						.getRepository("product_skus")
						.increment({ id: sku.id }, "availableStock", item.quantity);

					this.logger.log(
						`商品 ${item.productId} 的SKU ${sku.id} 库存恢复 ${item.quantity}`
					);
				} else {
					this.logger.warn(`商品 ${item.productId} 没有SKU，无法恢复库存`);
				}
			}
		}
	}

	// 减少可用库存（创建订单时调用）
	private async reduceAvailableStock(items: any[]): Promise<void> {
		for (const item of items) {
			// 如果有SKU，减少SKU的可用库存
			if (item.skuId) {
				await this.orderRepository.manager
					.getRepository("product_skus")
					.decrement({ id: item.skuId }, "availableStock", item.quantity);
				this.logger.log(`SKU ${item.skuId} 可用库存减少 ${item.quantity}`);
			} else {
				// 如果没有SKU，找到商品的SKU进行操作
				const product = await this.productService.findOne(item.productId);
				if (product.skus && product.skus.length > 0) {
					// 如果有SKU，分配数量到第一个有足够库存的SKU
					for (const sku of product.skus) {
						if (sku.availableStock >= item.quantity) {
							await this.orderRepository.manager
								.getRepository("product_skus")
								.decrement({ id: sku.id }, "availableStock", item.quantity);
							this.logger.log(
								`商品 ${item.productId} 的SKU ${sku.id} 可用库存减少 ${item.quantity}`
							);
							break;
						}
					}
				} else {
					this.logger.warn(`商品 ${item.productId} 没有SKU，无法减少可用库存`);
				}
			}
		}
	}

	// 恢复可用库存（创建订单失败时调用）
	private async restoreAvailableStock(items: any[]): Promise<void> {
		for (const item of items) {
			// 如果有SKU，恢复SKU的可用库存
			if (item.skuId) {
				await this.orderRepository.manager
					.getRepository("product_skus")
					.increment({ id: item.skuId }, "availableStock", item.quantity);
				this.logger.log(`SKU ${item.skuId} 可用库存恢复 ${item.quantity}`);
			} else {
				// 如果没有SKU，找到商品的SKU进行操作
				const product = await this.productService.findOne(item.productId);
				if (product.skus && product.skus.length > 0) {
					// 恢复第一个SKU的可用库存（或者找到之前扣减的SKU）
					const sku = product.skus[0];
					await this.orderRepository.manager
						.getRepository("product_skus")
						.increment({ id: sku.id }, "availableStock", item.quantity);
					this.logger.log(
						`商品 ${item.productId} 的SKU ${sku.id} 可用库存恢复 ${item.quantity}`
					);
				} else {
					this.logger.warn(`商品 ${item.productId} 没有SKU，无法恢复可用库存`);
				}
			}
		}
	}

	async remove(id: number): Promise<void> {
		const order = await this.findOne(id);

		// 如果订单状态为待付款，直接删除
		if (order.status === "待付款") {
			await this.orderRepository.remove(order);
			return;
		}

		// 其他状态的订单不能删除
		throw new BadRequestException("只能删除待付款状态的订单");
	}

	// 测试方法，用于检查订单项数据
	async getOrderItems(): Promise<any> {
		// 获取所有订单项
		const orderItems = await this.orderItemRepository.find({
			relations: ["product"],
		});

		// 获取所有订单
		const orders = await this.orderRepository.find({
			relations: ["items", "items.product"],
		});

		return {
			orderItems,
			orders,
			orderItemsCount: orderItems.length,
			ordersCount: orders.length,
		};
	}
}
